<?php

namespace App\Http\Controllers\V1;

use Throwable;
use App\Support\Code;
use App\Support\Config;
use App\Models\Address;
use App\Jobs\GetEthValue;
use App\Models\EthRecord;
use App\Models\YecRecord;
use App\Support\Currency;
use Illuminate\Support\Arr;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Facades\Storage;
use App\Http\Resources\RechargeCollection;
use SimpleSoftwareIO\QrCode\Facades\QrCode;

class RechargeController extends ApiController
{
    public function index()
    {
        $user = $this->getUser();

        $eth = EthRecord::select([
            'status',
            'created_at',
            'updated_at',
            'enable_value',
            DB::raw('0 AS enable_yecs_value'),
            DB::raw('"ETH" AS currency_1'),
            'to_address_id AS address_id'
        ])->where('type', EthRecord::TYPE_RECHARGE)
            ->where('user_id', $user->id)->orderByDesc('created_at');

        $query = YecRecord::select([
            'status',
            'created_at',
            'updated_at',
            'enable_value',
            'enable_yecs_value',
            DB::raw('"YEC" AS currency_1'),
            'from_address_id AS address_id',
        ])->where('type', YecRecord::TYPE_RECHARGE)
            ->where('user_id', $user->id)->orderByDesc('created_at')->union($eth);

        return $this->success(new RechargeCollection($query->paginate(100)));
    }

    /**
     * 充值接口
     *
     * @param  Request  $request
     * @return \Illuminate\Http\JsonResponse
     * @throws Throwable
     */
    public function store(Request $request)
    {
        $data = Arr::only($request->all(), [
            'value',
            'to_address_id',
        ]);
        $data['user_id'] = $this->getUser()->id;
        if ($request->currency == Currency::YEC) {
            $data['enable_value'] = $data['value'];
            $data['type'] = YecRecord::TYPE_RECHARGE;
            $data['enable_value'] = $data['value'] * 0.8;
            $data['from_address_id'] = $request->from_address_id;
            $data['enable_yecs_value'] = $data['value'] * 0.2 * Config::getYecYecsRatio();
            $getRecharge = Config::getRecharge();
          
            try {
                DB::transaction(function () use ($data, $getRecharge) {
                    if ($getRecharge['quota_surplus'] < $data['value']) {
                        $data['status'] = YecRecord::STATUS_QUOTA;
                        $new_quota_surplus = 0;
                    } else {
                        $new_quota_surplus = big_number($getRecharge['quota_surplus'])->subtract($data['value']);
                    }
                    $getRecharge->quota_surplus = $new_quota_surplus;
                    $getRecharge->save();
                    YecRecord::create($data);
                });
            } catch (Throwable $exception) {
                Log::error($exception->getMessage());
                throw $exception;
            }
        } elseif ($request->currency == Currency::ETH) {
            $now = now();
            if ($data['value'] < 0.05) {
                return $this->fail(Code::PARAMETER_ERROR, '最小可充值 0.05 ！');
            }
            $data['enable_value'] = $data['value'] - 0.005;
            $data['status'] = EthRecord::STATUS_ETH_CONFIRMED;
            $ethRecord = EthRecord::create($data);
            dispatch(new GetEthValue($ethRecord));
            dispatch(new GetEthValue($ethRecord))->delay($now->addMinutes(5));
            dispatch(new GetEthValue($ethRecord))->delay($now->addMinutes(10));
            dispatch(new GetEthValue($ethRecord))->delay($now->addMinutes(15));
        }

        return $this->setMsg('充值成功')->success();
    }

    /**
     * @param  Request  $request
     * @return \Illuminate\Http\JsonResponse
     * @throws \App\Exceptions\ConfigNotSetException
     */
    public function rules(Request $request)
    {
        if ($request->currency == Currency::YEC) {
            $address = Config::getYecAddress();

            if (!$address) {
                return $this->fail(Code::SERVER_ERROR, '平台地址未设置');
            }

            $data = [
                'qrcode' => $address->qrcode,
                'address_id' => $address->id,
                'address' => $address->address,
            ];
            $data['yec_yecs_ratio'] = 0.2 * Config::getYecYecsRatio();
            $data['quota_surplus'] = Config::getRecharge()->quota_surplus;
        } else {
            $data = $this->getAdminEthAddress();
        }

        return $this->success($data);
    }

    /**
     * 获取平台的 Eth 地址
     */
    private function getAdminEthAddress()
    {
        $address = Address::where('type', 0)
            ->where('user_id', $this->getUser()->id)
            ->where('currency', Currency::ETH)->first();

        if ($address->qrcode) {
            $file = $address->qrcode;
        } else {
            $file = 'qrcodes/' . $address->address . '.png';

            Storage::disk('public')->put(
                $file,
                QrCode::format('png')->size(224)->generate($address->address)
            );

            $file = storage_url($file);
            $address->qrcode = $file;
            $address->save();
        }

        return [
            'qrcode' => $file,
            'address_id' => $address->id,
            'address' => $address->address,
        ];
    }
}
